git 的内容存储使用的是 SHA-1 哈希算法,它是分布式的。
工作流
本地仓库由 git 维护的三棵“树”组成:
- 工作区:实际文件,当前目录,不算目录下的
.git
(这是版本库) - 暂存区(Index):它像个缓存区域,临时保存你的改动,临时的二进制文件(.git/index)
- HEAD:它指向你最后一次提交的结果。实际是指向 master 分支的一个”游标”
基本工作流程
- 修改当前工作目录内容
- 使用
git add 指令目录
把指令目录下的修改添加到暂存区 - 使用
git commit -m "提交信息"
把暂存区中内容提交到本地仓库,即 HEAD - 使用
git push 远方仓库链接
把 HEAD 最新内容推送到指定远方仓库
分支
分支是用来将功能开发隔绝开来的。在你创建仓库的时候,master 是默认分支。通常的做法是在其他分支上进行开发,完成后再将它们合并到主分支 master 上。使用分支意味着你可以从开发主线上分离开来,然后在不影响主线的同时继续工作。
一些名词
名词 | 解释 |
---|---|
workspace | 工作区 |
local repository | 版本库或本地仓库 |
remote repository | 远程仓库 |
conflicts | 冲突 |
origin | 远程仓库链接的别名,是在 clone 一个托管在服务器上代码库时,git 默认创建的指向这个远程代码库的标签,origin 指向的就是本地的代码库托管在服务器上的版本。在命令行中出现的 origin,指操作是对远程仓库操作 |
master | 新仓库的默认分支通常被命名为 master,但在后续版本中,Git 开始鼓励使用其他名称(如 main),以避免与种族主义相关的词汇。使用 –initial-branch 参数,你可以自定义这个初始分支的名称,比如: git init --initial-branch=main |
merge | 合并 |
fetch | 获取 |
tag | 标签 |
index | 索引(暂存区),一般存放在 .git 目录下的 index 文件(.git/index)中,所以我们把暂存区有时也叫作索引(index) |
stage | 暂存区,与 index 一个意思 |
版本库 | 工作区有一个隐藏目录 .git,这个不算工作区,而是 Git 的版本库 |
.gitignore | 为 git 列出需要忽略的文件,每个子文件都可以建立该文件屏蔽一些文件 |
.gitkeep | 保持空文件的社区约定,详细可参考 这里 |
常用的提交信息格式
关于 commit 提交信息,每个团队都有自己的格式,比较常用的是这个:
<type>(scope) Subject...
#例如,在 arm 中添加新功能 giv3:
<feat>(arch/arm) Add giv3 control
type 取值参考如下:
值 | 含义 |
---|---|
feat | 添加新功能(feature) |
fix | 修复 BUG(fix up) |
test | 测试(test) |
doc | 添加文档(documention) |
git 配置
git 提供了一个叫做 git config 的工具,专门用来配置或读取相应的工作环境变量。这些环境变量,决定了 git 在各个环节的具体工作方式和行为。这些变量可以存放在以下三个不同的地方:
/etc/gitconfig
文件:系统中对所有用户都普遍适用的配置。若使用git config
时用--system
选项,读写的就是这个文件。~/.gitconfig
文件:用户目录下的配置文件只适用于该用户。若使用git config
时用--global
选项,读写的就是这个文件。- 当前项目的 git 目录中的配置文件(也就是工作目录中的
.git/config
文件):这里的配置仅仅针对当前项目有效。每一个级别的配置都会覆盖上层的相同配置,所以.git/config
里的配置会覆盖/etc/gitconfig
中的同名变量。 - 在 Windows 系统上,git 会找寻用户主目录下的
.gitconfig
文件。主目录即 $HOME 变量指定的目录,一般都是C:\Documents and Settings\$USER
。
此外,git 还会尝试找寻 /etc/gitconfig
文件,只不过看当初 git 装在什么目录,就以此作为根目录来定位。
$ git config --global -e
- 打开编辑器编辑配置,不加
--global
则针对当前
$ git config --global user.name "用户名"
$ git config --global user.email "电子邮箱"
- 如果用了 –global 选项,那么更改的配置文件就是位于你用户主目录下的那个,以后你所有的项目都会默认使用这里配置的用户信息。
- 如果要在某个特定的项目中使用其他名字或者电邮,只要去掉 –global 选项重新配置即可,新的设定保存在当前项目的 .git/config 文件里。
$ git config --global core.editor emacs
- 设置 git 默认使用的文本编辑器, 一般可能会是 Vi 或者 Vim。如果你有其他偏好,比如 Emacs 的话,可以重新设置。
$ git config --global merge.tool vimdiff
- 在解决合并冲突时使用哪种差异分析工具。
$ git config --list
http.postbuffer=2M
user.name=用户名
user.email=电子邮箱
- 要检查已有的配置信息,有时候会看到重复的变量名,那就说明它们来自不同的配置文件。
$ git config user.name
- 直接查阅某个环境变量的设定,只要把特定的名字跟在后面即可。
请参考
命令记录
gitk
内建的图形化 git
git init
初始化当前目录作为 git 仓库
git init newrepo
初始化指令目录 newrepo 为 git 仓库git init --initial-branch=main
git 会创建一个新的仓库,并将 main 设置为默认的分支
git add .
当前路径下的修改添加到暂存区
git commit -m “提交信息”
提交暂存区中的信息到本地仓库
git add -a -m "提交信息"
自动提交本地修改,使用-a
标志(它指令提交本修改或已经删除的,不会将新文件提交)
git clone 远方仓库链接
从服务器克隆一个仓库到本地,可从 http
和 ssh
协议克隆
git clone -b 指定分支名 远方仓库链接
克隆仓库下来,并切换到指令分支
git reset
回退
git reset --soft 指定提交ID
将HEAD
指向指定提交,暂存区(索引)不变,当前目录不变git reset --mixed 指定提交ID
将HEAD
指向指定提交,暂存区(索引)改变,当前目录不变git reset --hard 指定提交ID
将HEAD
指向指定提交,暂存区(索引)改变,当前目录改变
可以任意通过该命令回到某个提交,它会将原来的 HEAD
存储在 ORIG_HEAD
中(.git/ORIG_HEAD)。
需要注意的是,使用 --hard
在一开始就要保存好修改,在一个干净的工作目录中操作,不然之后返回将丢失修改,除非你不需要最新的修改了。因为所有的回退,都是通过从对象文件中抽取,你没有提交保存到对象文件中,再次回来将丢失。
git remote -v
查看已添加的所有远程仓库及其URL
一个本地Git仓库可以添加多个远程仓库引用。每个远程仓库都有一个在本地定义的别名,通过这些别名,你可以方便地与不同的远程仓库进行交互,如拉取(pull)或推送(push)代码
git remote add 远方仓库名 远程仓库URL
为远程仓库 URL 指定一个远程仓库名。比如创建一个不同 origin 的 backupgit remote set-url 远方仓库名 远程仓库URL
为远方仓库名设置不同的 URL。比如修改 origin 原来的 URL 为新的 URL
远程仓库别名 | 远程仓库地址 |
---|---|
origin | 指向默认的主远程仓库(如 http://gitlab.123.com) |
backup | 指向新增的备用远程仓库(如 http://gitlab.456.com) |
- 后续可以通过这些别名与各自的远程仓库进行交互:
命令 | 操作 |
---|---|
git pull origin 分支名 | 从 origin 拉取更新 |
git push backup 分支名 | 推送到 backup |
git push
将本地仓库推送到默认远方仓库。通过 git remote add backup 远程仓库URL
方式添加远方仓库,然后通过 git push backup **分支名**
推送到远方仓库,这种方式可以将本地仓库与远方仓库联系起来。
git push 远方仓库链接
推送到指定的远方仓库--set-upstream
设置默认远方仓库链接git push origin --delete 指定分支
切到其他分支行,删除远程仓库的指定分支git merge master --allow-unrelated-histories
新建了一个仓库之后,把本地仓库与远程仓库进行关联提交、拉取的时候合并,出现错误可以添加这个选项--allow-unrelated-histories
git fetch origin 指定分支
将本机已经关联的远程仓库的最新变更拉取到本地仓库,只拉取不合并
git pull
将默认远方仓库拉取最新变更并合并本地
git pull
=git fetch
+git merge
拉取并合并git pull 远方仓库链接
将指定远方仓库拉取最新变更并合并本地
git format-patch HEAD^^
将最近的 2 个提交生成 patch,需要打包最近几个就添加几个 ^
git format-patch -1
打包最近的一个 patch,有几个就写几个git format-patch -n1 -n2
打包 n1 与 n2 之间的 patch
git am 文件名.patch
将生成的 patch 打入代码中
git am -abort
放弃以前的 am 信息git apply --check 文件名.patch
不应用修补程序,而是查看修补程序是否使用
git branch 新分支名
基于当前分支创建新分支
- 第一个分支,或主分支,被称之为
master
git branch -d 指定分支名
将指定分支删除git branch -a
不指定分支,则显示所有本地分支名git branch -r
查看远程分支
git checkout 分支名
切换到指定分支
git checkout -b 分支名
使用-b
可以先创建分支,然后切换到新分支git checkout 指定文件
将暂存区的指定文件恢复到工作目录与git restore 指定文件
类似
git merge 指定分支名
将指定分支的修改合并到当前分支
git checkout master
git merge test
即,切换到主分支,然后将 test 分支合并到主分支
git diff 源分支名 目标分支名
显示两个分支差异,即暂存区和工作区的差异。
-
git diff
显示在工作目录且未暂存的变更 -
git diff -cache
显示已经暂存的差异
git tag 1.0.0 <sha1 ID>
给指定 ID 创建名为 1.0.0
标签(或版本号)
达到一个重要的阶段,并希望永远记住那个特别的提交快照,则可以添加标签
* git tag
查看所有标签
-
git tag -a 标签名 -m "标签注解"
可以使用-a
创建一个带注解的标签,不使用则不会记录一些信息 -
sha1 ID
在使用 ID 时,可以简写前几位,只要具有唯一性
git log
查看提交记录
git log -n3
查看最后提交的 3 个提交-p
显示提交的补丁(具体更改内容)。--oneline
以简洁的一行格式显示提交信息。--graph
以图形化方式显示分支和合并历史。--decorate
显示分支和标签指向的提交。--author=<作者>
只显示特定作者的提交。--since=<时间>
只显示指定时间之后的提交。--until=<时间>
只显示指定时间之前的提交。--grep=<模式>
只显示包含指定模式的提交消息。--no-merges
不显示合并提交。--stat
显示简略统计信息,包括修改的文件和行数。--abbrev-commit
使用短提交哈希值。--pretty=<格式>
使用自定义的提交信息显示格式。